package dht;

import dht.entity.Message;
import dht.entity.NodeInfo;
import dht.log.LogUtils;
import dht.socket.SocketHandler;
import dht.socket.TcpConnection;

public abstract class AbstractTransactionHandler implements ITransactionHandler {

	protected NodeInfo localInfo;
	protected NodeInfo remoteInfo;
	protected TcpConnection tcpConnection;
	protected SocketHandler socketHandler;

	protected boolean isInitiative;
	protected Message msg;

	public AbstractTransactionHandler(NodeInfo localInfo, NodeInfo remoteInfo,
			TcpConnection tcpConnection) {
		this.localInfo = localInfo;
		this.remoteInfo = remoteInfo;
		this.tcpConnection = tcpConnection;
	}

	public AbstractTransactionHandler(NodeInfo localInfo,
			SocketHandler socketHandler, TcpConnection tcpConnection) {
		this.localInfo = localInfo;
		this.socketHandler = socketHandler;
		this.tcpConnection = tcpConnection;
	}

	@Override
	public void handleInitiativeTransaction(Message msg, boolean isSync) {
		this.isInitiative = true;
		this.msg = msg;
		if (isSync) {
			handleTransaction();
		} else {
			new Thread(this).start();
		}
	}

	@Override
	public void handlePassiveTransaction(boolean isSync) {
		this.isInitiative = false;
		this.msg = null;
		if (isSync) {
			handleTransaction();
		} else {
			new Thread(this).start();
		}
	}

	@Override
	public void run() {
		handleTransaction();
	}

	protected void handleTransaction() {
		if (isInitiative) {
			long startTime = System.currentTimeMillis();
			LogUtils.infoLog("Type: " + msg.getMsgType() + " Id: "
					+ msg.getTransactionId() + " Start Time: " + startTime);
			runInitiative(msg);
			long endTime = System.currentTimeMillis();
			LogUtils.infoLog("Type: " + msg.getMsgType() + " Id: "
					+ msg.getTransactionId() + " End Time: " + endTime);
			LogUtils.infoLog("Type: " + msg.getMsgType() + " Id: "
					+ msg.getTransactionId() + " Total Time: "
					+ (endTime - startTime));
		} else {
			runPassive();
		}

	}

	protected abstract void runInitiative(Message msg);

	protected abstract void runPassive();

}
